package BeenChina.PM.Action;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.struts2.ServletActionContext;

import net.sf.json.JSONArray;
import BeenChina.PM.Model.ModelQualityCheckBaseInfo;
import BeenChina.PM.Model.ModelQualityCheckBaseView;
import BeenChina.PM.Model.ModelQualityCheckMissTypeInfo;
import BeenChina.PM.Model.ModelQualityCheckMissTypeView;
import BeenChina.PM.Model.ModelUser;
import BeenChina.PM.Service.ServiceFactory;
import BeenChina.PM.Util.EncodeDownLoadFileName;
import BeenChina.PM.Util.ExportInfo;
import BeenChina.PM.Util.ExportToExcel;
import BeenChina.PM.Util.StringUtil;
import BeenChina.PM.Util.xmlSerializer;

import com.opensymphony.xwork2.ActionContext;
import com.opensymphony.xwork2.ActionSupport;

public class QualityCheckQueryAction extends ActionSupport {

	private static final long serialVersionUID = 1L;
	private String dateTo;
	private Integer dataTypeIndex;
	private Map<String, Object> tableData;
	private InputStream excelStream;
	private String fileName;
	private static String EXPORTID = "491";
	private boolean exportExcel;
	private static final Log log = LogFactory
			.getLog(QualityCheckQueryAction.class);
	private String[] dataType = { "文字", "数字" };

	public boolean isExportExcel() {
		return exportExcel;
	}

	public InputStream getExcelStream() {
		return excelStream;
	}

	public void setExcelStream(InputStream excelStream) {
		this.excelStream = excelStream;
	}

	public String getFileName() throws UnsupportedEncodingException {
		ServletActionContext.getResponse().setHeader("charset", "UTF-8");
		fileName = EncodeDownLoadFileName.encode(
				ServletActionContext.getRequest(), fileName);
		return fileName;
	}

	public void setFileName(String fileName) {
		this.fileName = fileName;
	}

	public void setDataTypeIndex(Integer dataTypeIndex) {
		this.dataTypeIndex = dataTypeIndex;
	}

	public String getDataType() {
		return dataType[dataTypeIndex];
	}

	public Map<String, Object> getTableData() {
		return tableData;
	}

	public void setDateTo(String dateTo) {
		this.dateTo = dateTo;
	}

	@Override
	public String execute() {
		ModelUser user = (ModelUser) ActionContext.getContext().getSession()
				.get("user");
		if (user != null)
			exportExcel = user.concatPermission(EXPORTID);
		return "load";
	}

	public List<ModelQualityCheckBaseInfo> getBaseInfos() throws Exception {
		try {
			if (!getDataType().isEmpty()
					&& StringUtil.isDate(dateTo, "yyyy-MM")) {
				return ServiceFactory.getInstance()
						.getCaseProductionInfoService()
						.selectQualityCheckBaseInfo(dateTo, getDataType());
			} else {
				return null;
			}
		} catch (Exception exp) {
			throw exp;
		}
	}

	public List<ModelQualityCheckMissTypeInfo> getMissTypeInfos()
			throws Exception {
		try {
			if (!getDataType().isEmpty()
					&& StringUtil.isDate(dateTo, "yyyy-MM")) {
				return ServiceFactory.getInstance()
						.getCaseProductionInfoService()
						.selectQualityCheckMissTypeInfo(dateTo, getDataType());
			} else {
				return null;
			}
		} catch (Exception exp) {
			throw exp;
		}
	}

	public List<ModelQualityCheckMissTypeView> getMissTypeViews()
			throws Exception {
		try {
			if (!getDataType().isEmpty()
					&& StringUtil.isDate(dateTo, "yyyy-MM")) {
				return ServiceFactory.getInstance()
						.getCaseProductionInfoService()
						.selectQualityCheckMissTypeView(dateTo, getDataType());
			} else {
				return null;
			}
		} catch (Exception exp) {
			throw exp;
		}
	}

	public String refreshData() throws Exception {

		List<ModelQualityCheckBaseInfo> baseInfos = getBaseInfos();
		List<ModelQualityCheckMissTypeInfo> missTypeInfos = getMissTypeInfos();
		List<ModelQualityCheckMissTypeView> missTypeViews = getMissTypeViews();

		Map<String, Object> map = new HashMap<String, Object>();
		map.put("TableBaseInfo", getBaseInfoTable(baseInfos));
		map.put("TableMissTypeInfo", getMissTypeInfoTable(missTypeInfos));

		Map<String, JSONArray> baseInfoViewMap = getBaseInfoChart(baseInfos);

		Iterator<Entry<String, JSONArray>> iter = baseInfoViewMap.entrySet()
				.iterator();
		while (iter.hasNext()) {
			Map.Entry<String, JSONArray> entry = (Map.Entry<String, JSONArray>) iter
					.next();
			map.put(entry.getKey(), entry.getValue());
		}

		Map<String, JSONArray> missTypeInfoViewMap = getMissTypeInfoChart(missTypeViews);
		iter = missTypeInfoViewMap.entrySet().iterator();
		while (iter.hasNext()) {
			Map.Entry<String, JSONArray> entry = (Map.Entry<String, JSONArray>) iter
					.next();
			map.put(entry.getKey(), entry.getValue());
		}
		tableData = map;
		return ActionSupport.SUCCESS;
	}

	private Map<String, JSONArray> getBaseInfoChart(
			List<ModelQualityCheckBaseInfo> list) {
		Map<String, JSONArray> map = new HashMap<String, JSONArray>();

		if (list == null || list.size() == 0) {
			return map;
		}

		ArrayList<String> cases = new ArrayList<String>();

		String firstItem = list.get(0).getCaseName();

		for (ModelQualityCheckBaseInfo model : list) {
			String nextItem = model.getCaseName();
			if (!nextItem.equals(firstItem)) {

				cases.add(firstItem);
				firstItem = nextItem;

			}
		}
		cases.add(firstItem);

		// 循环获得图表数据
		for (String caseName : cases) {

			// 获得图表数据
			List<ModelQualityCheckBaseView> views = ServiceFactory
					.getInstance()
					.getCaseProductionInfoService()
					.selectQualityCheckBaseView(dateTo, getDataType(), caseName);

			// 获得图表数据的数据项目
			ArrayList<String> categoryNames = new ArrayList<String>();
			firstItem = views.get(0).getCategoryName();
			for (ModelQualityCheckBaseView modelView : views) {
				String nextItem = modelView.getCategoryName();
				if (!nextItem.equals(firstItem)) {
					categoryNames.add(firstItem);
					firstItem = nextItem;
				}
			}
			categoryNames.add(firstItem);

			for (String categoryName : categoryNames) {
				JSONArray jsonItem = new JSONArray();
				for (ModelQualityCheckBaseView modelView : views) {

					if (modelView.getCategoryName().equals(categoryName)) {

						if (modelView.getDataInfo() != null){
							JSONArray json = new JSONArray();
							json.add(modelView.getDate());
							json.add(modelView.getDataInfo());
	
							jsonItem.add(json);
					    }
					}

				}

				map.put(caseName + categoryName, jsonItem);
			}

		}
		return map;

	}

	private JSONArray getBaseInfoDetailTable(
			List<ModelQualityCheckBaseInfo> list) {

		JSONArray map = new JSONArray();

		if (list == null || list.size() == 0) {
			return map;
		}

		JSONArray jsonTittle = new JSONArray();
		jsonTittle.add("Date");
		jsonTittle.add("CategoryName");

		String firstItem = list.get(0).getCaseName();

		for (ModelQualityCheckBaseInfo model : list) {
			String nextItem = model.getCaseName();
			if (!nextItem.equals(firstItem)) {
				jsonTittle.add(firstItem);
				firstItem = nextItem;
			}
		}
		jsonTittle.add(firstItem);

		map.add(jsonTittle);

		for (int i = 1; i < jsonTittle.size(); i++) {

			// 循环获得图表数据
			String caseName = jsonTittle.get(i).toString();

			// 获得图表数据
			List<ModelQualityCheckBaseView> views = ServiceFactory
					.getInstance()
					.getCaseProductionInfoService()
					.selectQualityCheckBaseView(dateTo, getDataType(), caseName);

			for (int j = 0; j < views.size(); j++) {

				ModelQualityCheckBaseView modelView = views.get(j);

				JSONArray json = null;
				boolean newItem = false;

				if (map.size() < j + 2) {

					map.add(new JSONArray());
					newItem = true;
				}

				json = map.getJSONArray(j + 1);

				if (newItem) {
					json.add(modelView.getDate());
					json.add(modelView.getCategoryName());
				}
				 
				if (modelView.getDataInfo() ==null)
					json.add("");
				else	
				 json.add(modelView.getDataInfo());

			}
		}

		return map;

	}

	private Map<String, JSONArray> getMissTypeInfoChart(
			List<ModelQualityCheckMissTypeView> list) {
		Map<String, JSONArray> map = new HashMap<String, JSONArray>();

		if (list == null || list.size() == 0) {
			return map;
		}

		ArrayList<String> missTypes = new ArrayList<String>();

		String firstItem = list.get(0).getMissType();

		for (ModelQualityCheckMissTypeView model : list) {
			String nextItem = model.getMissType();
			if (!nextItem.equals(firstItem)) {
				missTypes.add(firstItem);
				firstItem = nextItem;
			}
		}
		missTypes.add(firstItem);

		// 循环获得图表数据
		for (String missType : missTypes) {

			JSONArray jsonItem = new JSONArray();
			for (ModelQualityCheckMissTypeView modelView : list) {

				if (modelView.getMissType().equals(missType)) {

					if (modelView.getDataInfo() !=null){
						JSONArray json = new JSONArray();
						json.add(modelView.getDate());
						json.add(modelView.getDataInfo());
	
						jsonItem.add(json);
					}
				}
			}

			map.put(missType, jsonItem);

		}
		return map;

	}

	private JSONArray getMissTypeInfoDetailTable(
			List<ModelQualityCheckMissTypeView> list) {
		JSONArray mapTable = new JSONArray();

		if (list == null || list.size() == 0) {
			return mapTable;
		}

		ArrayList<String> dates = new ArrayList<String>();

		JSONArray jsonTittle = new JSONArray();
		jsonTittle.add("Date");

		String firstItemType = list.get(0).getMissType();
		//String firstItemDate = list.get(0).getDate();

		for (ModelQualityCheckMissTypeView model : list) {
			String nextItemType = model.getMissType();
			if (!nextItemType.equals(firstItemType)) {
				jsonTittle.add(firstItemType);
				firstItemType = nextItemType;
			}

			//String nextItemDate = model.getDate();
			if (dates==null || !dates.contains(model.getDate())){
			//if (!nextItemDate.equals(firstItemDate)) {
				dates.add(model.getDate());
				//firstItemDate = nextItemDate;
			}

		}
		jsonTittle.add(firstItemType);
		//dates.add(firstItemDate);
		mapTable.add(jsonTittle);

		// 循环获得图表数据
		for (String date : dates) {

			JSONArray json = new JSONArray();
			json.add(date);

			for (int i = 1; i < jsonTittle.size(); i++) {

				String missType = jsonTittle.get(i).toString();

				for (ModelQualityCheckMissTypeView modelView : list) {

					if (modelView.getMissType().equals(missType)
							&& modelView.getDate().equals(date)) {

						if (modelView.getDataInfo() ==null)
						   json.add("");
						else
						   json.add(modelView.getDataInfo());
					}
				}
			}
			mapTable.add(json);
		}

		return mapTable;

	}

	private JSONArray getBaseInfoTable(List<ModelQualityCheckBaseInfo> list) {

		JSONArray mapTable = new JSONArray();
		if (list == null || list.size() == 0) {
			return mapTable;
		}

		JSONArray jsonTittle = new JSONArray();
		jsonTittle.add("項目");
		jsonTittle.add("単位");

		String firstItem = list.get(0).getCaseName();

		for (ModelQualityCheckBaseInfo model : list) {
			String nextItem = model.getCaseName();
			if (!nextItem.equals(firstItem)) {

				jsonTittle.add(firstItem);
				firstItem = nextItem;

			}
		}
		jsonTittle.add(firstItem);
		mapTable.add(jsonTittle);

		firstItem = list.get(0).getCaseName();
		List<ModelQualityCheckBaseInfo> resultHeader = new ArrayList<ModelQualityCheckBaseInfo>();
		for (int i = 0; i < list.size(); i++) {
			ModelQualityCheckBaseInfo model = list.get(i);

			if (model.getCaseName().equals(firstItem)) {
				resultHeader.add(model);
			}
		}

		for (int i = 0; i < resultHeader.size(); i++) {
			ModelQualityCheckBaseInfo modelH = resultHeader.get(i);

			JSONArray json = new JSONArray();

			json.add(modelH.getCategoryName());
			json.add(modelH.getCategoryUnit());

			for (int j = 0; j < list.size(); j++) {
				ModelQualityCheckBaseInfo model = list.get(j);

				if (modelH.getCategoryName().equals(model.getCategoryName())
						&& modelH.getCategoryUnit().equals(
								model.getCategoryUnit())) {

					/*
					 * if (model.getCategoryName().equals("検査合格率") ||
					 * model.getCategoryName().equals("6ヶ月間平均合格率") ||
					 * model.getCategoryName().equals("本年度累計合格率") ){
					 * json.add(model.getDataInfo() + '%'); }
					 */

					json.add(model.getDataInfo());

				}
			}

			mapTable.add(json);
		}

		return mapTable;
	}

	private JSONArray getMissTypeInfoTable(
			List<ModelQualityCheckMissTypeInfo> list) {
		JSONArray mapTable = new JSONArray();
		if (list == null || list.size() == 0) {
			return mapTable;
		}

		JSONArray jsonTittle = new JSONArray();
		jsonTittle.add("分類");
		jsonTittle.add("項目");

		String firstItem = list.get(0).getMissType();

		for (ModelQualityCheckMissTypeInfo model : list) {
			String nextItem = model.getMissType();
			if (!nextItem.equals(firstItem)) {

				jsonTittle.add(firstItem);
				firstItem = nextItem;

			}
		}
		jsonTittle.add(firstItem);
		mapTable.add(jsonTittle);

		firstItem = list.get(0).getMissType();
		List<ModelQualityCheckMissTypeInfo> resultHeader = new ArrayList<ModelQualityCheckMissTypeInfo>();
		for (int i = 0; i < list.size(); i++) {
			ModelQualityCheckMissTypeInfo model = list.get(i);

			if (model.getMissType().equals(firstItem)) {
				resultHeader.add(model);
			}
		}

		for (int i = 0; i < resultHeader.size(); i++) {
			ModelQualityCheckMissTypeInfo modelH = resultHeader.get(i);

			JSONArray json = new JSONArray();
			json.add(modelH.getDataType());
			json.add(modelH.getCategoryName());

			for (int j = 0; j < list.size(); j++) {
				ModelQualityCheckMissTypeInfo model = list.get(j);

				if (modelH.getDataType().equals(model.getDataType())
						&& modelH.getCategoryName().equals(
								model.getCategoryName())) {

					json.add(model.getDataInfo());
				}
			}

			mapTable.add(json);
		}

		return mapTable;
	}

	public String export() throws Exception {
		try {
			String excelfile = "";
			String xmlfile = "";
			if ("文字".equals(getDataType())) {
				excelfile = "QualityCheckQuery_JP.xls";
				xmlfile = "QualityCheckQuery_JP.xml";
			} else if ("数字".equals(getDataType())) {
				excelfile = "QualityCheckQuery_Number.xls";
				xmlfile = "QualityCheckQuery_Number.xml";
			}

			//begin
			String file = ServletActionContext.getServletContext().getRealPath(
					"WEB-INF/excel/" + excelfile);

			List<ModelQualityCheckBaseInfo> baseInfos = getBaseInfos();
			List<ModelQualityCheckMissTypeInfo> missTypeInfos = getMissTypeInfos();
			List<ModelQualityCheckMissTypeView> missTypeViews = getMissTypeViews();

			Map<String, JSONArray> map = new HashMap<String, JSONArray>();
			map.put("合格率推算", getBaseInfoTable(baseInfos));
			map.put("類ミス率", getMissTypeInfoTable(missTypeInfos));
			map.put("合格率推算图表", getBaseInfoDetailTable(baseInfos));
			map.put("類ミス率图表", getMissTypeInfoDetailTable(missTypeViews));

			// TODO:图表数据准备

			ByteArrayOutputStream out = new ByteArrayOutputStream();
			this.setFileName("サンフルチェック検索【" + getDataType()+ "】_" + this.dateTo );
			String infoFile = ServletActionContext.getServletContext()
					.getRealPath("WEB-INF/excel/" +xmlfile);
			List<ExportInfo> infoList = (new xmlSerializer<List<ExportInfo>>())
					.read(infoFile);

			ExportToExcel.export(file, map, infoList, out);

			setExcelStream(new ByteArrayInputStream(out.toByteArray()));
			out.close();

			return ActionSupport.SUCCESS;
		} catch (Exception exp) {
			log.error(exp);
			return ActionSupport.ERROR;
		}
	}

}
